#include "../../FS/fs.client.h"
#include "fs.h"
#include "../gui.menu.h"
#include "../gui.text.h"
#include "../gui.button.h"

TOB::UI_FS::UI_FS(UIConfig &c): Mod(c) {
}

TOB::UI_FS::~UI_FS() {
}

void TOB::UI_FS::run() {
  // Define ui
  UIMenu menum(0, 1, config.offsetX, 0);
  UIWindow statusw(0, 0, 0, 1);
  UIWindow textw(config.offsetX, 0, 0, 0);

  // Assign temp objects
  this->statusw = &statusw;
  this->textw = &textw;

  menum.insert(config.lang["back"], [&](){ 
    menum.running = false; 
  });

  // Upload file menu
  menum.insert(config.lang["upload"], [&](){
    status(config.lang["upload"]);
    textw.setCursor(config.offsetX + 1, 2);
    textw.clearLine();
    textw.putString(config.lang["fs-file"]);

    // UI elements
    UIText filet(config.offsetX + config.offsetX + 1, 3, 0, 1);
    UIMenu uploadm(config.offsetX, 1, config.offsetX, 0);

    // Back to filesharing menu
    uploadm.insert(config.lang["back"], [&](){
      uploadm.running = false;
    });

    // Enter filename
    uploadm.insert(config.lang["enter"], [&](){
      filet.focus();     
      uploadm.showCursor(false);
    });

    // Upload file
    uploadm.insert(config.lang["upload"], [&](){
      FS_Client fs(config.nsip, config.username, config.password);
      fs.onProgress = [&](float p, uint32 b) {
        progress(p);
      };

      // Start upload
      uint32 fileId;
      if((Code::Type)fs.upload(CONVERT(filet.lines[0]), &fileId) == Code::Okay) {
        StringStream stream;
        String ttl;
        stream << fileId;
        stream >> ttl;
        fileList.push_back(ttl);
        String tmp = config.lang["uploaded"] + ttl;
        status(tmp);
      } else {
        status(config.lang["fs-upload-error"]);
      }
    });

    // Run
    uploadm.focus();
  });

  std::function<void(String &id)> download = [&](String &id) {
    status(config.lang["download"]);
    textw.setCursor(config.offsetX + 1, 2);
    textw.clearLine();
    textw.putString(config.lang["fs-id"]);

    // UI elements
    UIText filet(config.offsetX + config.offsetX + 1, 3, 0, 1);
    UIMenu downloadm(config.offsetX, 1, config.offsetX, 0);

    filet.lines[0] = id;
    filet.printBlock();

    // Back to filesharing menu
    downloadm.insert(config.lang["back"], [&](){
      downloadm.running = false;
    });

    // Enter file id
    downloadm.insert(config.lang["enter"], [&](){
      filet.focus();     
      downloadm.showCursor(false);
    });

    // Download file
    downloadm.insert(config.lang["download"], [&](){
      FS_Client fs(config.nsip, config.username, config.password);
      fs.onProgress = [&](float p, uint32 b) {
        progress(p);
      };

      // Convert id
      StringStream stream(filet.lines[0]);
      uint32 fileId;
      stream >> fileId;
      std::string filename;

      // Download
      if((Code::Type)fs.download(fileId, filename, 
          CONVERT(config.config["fs-output"])) != Code::Okay) {
        status(config.lang["fs-download-error"]);
      } else {
        String tmp = config.lang["downloaded"] + CONVERT(filename);
        status(tmp);
      }
    });

    downloadm.focus();
  };

  // Download file
  menum.insert(config.lang["download"], [&](){
    String str;
    download(str);    
  });

  // List recently uploaded files
  menum.insert(config.lang["fs-list"], [&](){
    status(config.lang["fs-list"]);
    String *sid = 0;
    UIMenu listm(config.offsetX, 1, 0, 0);  
    listm.drawRest = false;
    listm.insert(config.lang["back"], [&](){ listm.running = false; });
    for(String &id: fileList) {
      listm.insert(id, [&](){
        sid = &id;
        listm.running = false;  
      });
    }
    listm.focus();
    if(sid) { download(*sid); }
  });

  String str;
  status(str);
  menum.focus();
}


// Set status
void TOB::UI_FS::status(String &msg) {
  statusw->setCursor(0, 0);
  statusw->clearLine();
  statusw->setColor(Color::Title);
  String out = config.lang["file-sharing"] + config.lang["delim"] + msg;
  statusw->putString(out);
}

// Set progress
void TOB::UI_FS::progress(Float percent) {
  String count;
  StringStream stream;
  stream << percent;
  stream >> count;
  String temp = count + config.lang["percent"];
  status(temp);
}
